Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Build JavaCPP libraries at compile time #20

Open
wants to merge 3 commits into
base: master
Choose a base branch
from

Conversation

thirstycrow
Copy link

It would be more convenient to build the JavaCPP libs at compile time, so we don't have to setup a C++ build environment at every deploy site.

@@ -1,34 +1,40 @@
package org.bytedeco.sbt.javacpp

import scala.language.postfixOps
import sbt._
import org.bytedeco.javacpp.tools.Builder
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Stupid question: this Builder , which is a plugin-level JavaCPP Builder with a set version based on

libraryDependencies += "org.bytedeco" % "javacpp" % "1.4.3"

, isn't necessarily going to support the classes brought in by ""org.bytedeco" % "javacpp" % Versions.javaCppVersion jar", which is a project-level, right?

Copy link
Author

@thirstycrow thirstycrow Oct 7, 2019

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Because Versions.javaCppVersion is deducted from the filename from which the Builder class is loaded, it should be the same as what is set in set-javacpp/build.sbt, or project/plugins.sbt of the user project. So the same version of JavaCpp library should be used by the user project and the plugin, unless the user specified a different version in build.sbt instead of project/plugins.sbt. I updated the README documentation on how to specify a different JavaCPP version. It is a breaking change though. A consistency check can be added before JavaCPP build, and print a warning if the library versions do not match.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@thirstycrow Does that mean we can remove that line with JavaCPP 1.4.3 from sbt-javacpp/built.sbt?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No, the JavaCPP library is required by both the user project (to define the JavaCPP classes) and the sbt-javacpp plugin (to build the JNI codes).

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok, so let's set them to the same version?

Copy link
Member

@lloydmeta lloydmeta left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

As discussed, we'd need a way to catch and warn the user if the library versions between the build version and dependency versions don't match. Or even perhaps warn if they're incompatible (maybe different minor version? Not sure what build assurances JavaCPP itself provides across versions (cc @saudet), e.g. is JavaCPP 1.5.x reasonably guaranteed to be able to .build() things from all 1.5,x (and fail reliably if it can't)?

README.markdown Outdated

```scala
javaCppVersion := "1.4.3"
libraryDependencies += "org.bytedeco" % "javacpp" % "1.5.1"
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'd much prefer the mechanism for specifying a different javacpp version to remain the same as it is now: setting a new version, rather than straight up requiring someone to declare the whole dependency. It's both simpler and backwards compatible.

@saudet
Copy link
Member

saudet commented Oct 23, 2019

I'm not sure I understand, in which circumstances would we need to use 2 different versions of JavaCPP together? I suppose they can get loaded in 2 different class loaders, but then how do they interact?

@thirstycrow thirstycrow force-pushed the build-at-compile-time branch 2 times, most recently from 1eb0850 to c2e05a1 Compare October 24, 2019 13:41
@thirstycrow thirstycrow force-pushed the build-at-compile-time branch from c2e05a1 to 0298ecd Compare October 24, 2019 13:46
@thirstycrow
Copy link
Author

I found a better way to implement the task, using reflection. In this way, the Builder instance is created reflectively using a Builder class loaded from the user project's classpath. I also transported some code from org.bytedeco.javacpp.Loader (which finds the current platform from the system properties), so that the javacpp library can be removed from the plugin's dependencies, thus avoids the potential version conflict, and the way of specifying the library version is kept the same with previous versions.

@saudet
Copy link
Member

saudet commented Oct 25, 2019 via email

@thirstycrow
Copy link
Author

I'm not very familiar with how maven works. Can you elaborate why extensions don't work for transitive dependencies with maven?

@saudet
Copy link
Member

saudet commented Oct 25, 2019

I think the idea with Maven is that extensions and plugins are only available at build time. When we pull in transitive dependencies, we are not building those, so their build time extensions and plugins don't get used.

@thirstycrow
Copy link
Author

Do you mean maven extensions and plugins cannot get a fully resolved dependency tree of the project?

@saudet
Copy link
Member

saudet commented Oct 25, 2019

No, at build time, they work fine. At runtime, they are not used, that's the problem.

@thirstycrow
Copy link
Author

I see. Sbt has nothing different on this with maven. Ideally, there could be a tiny library for common utilities required both at build time and runtime. For the moment, if you really care about the code duplication, adding javacpp as a dependency of the plugin should still work without conflict, unless the platform determining logic differs between versions used for build and runtime. Should I change it to this style?

@saudet
Copy link
Member

saudet commented Oct 25, 2019

Yeah, I don't know what's best. I'll leave it up to @lloydmeta

}

object autoImport {
type JavaCppBuilder = {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If the real org.bytedeco.javacpp.tools.Builder is updated/changed (e.g. when the user configures a newer version), would this still work?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It should work as long as the corresponding methods that are actually invoked are not missing in the newer version of org.bytedeco.javacpp.tools.Builder.

import scala.language.{ postfixOps, reflectiveCalls }
import scala.util.Try

object JavaCppPlugin extends AutoPlugin {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why did you create a new file?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is not required. But when there is another Plugin object, which I'd like to enable/disable, I would not have to specify the package.

@@ -20,7 +17,28 @@ object Platform {
*/
val current: Seq[String] = sys.props.get(platformOverridePropertyKey) match {
case Some(platform) if platform.trim().nonEmpty => platform.split(' ')
case _ => Seq(Loader.getPlatform)
case _ =>
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What's the advantage of not pulling in JavaCpp at the sbt level and re-using the loader?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I chose this style, so I didn't have to think about whether the potential difference of the libraries would cause any trouble. It should work either way, though.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants